package sr.myserver.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import io.jsonwebtoken.Claims;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import sr.myserver.commons.Result;
import sr.myserver.commons.StrUtils;
import sr.myserver.config.JwtConfig;
import sr.myserver.entity.SysButtons;
import sr.myserver.entity.SysMenus;
import sr.myserver.entity.SysRoleMenu;
import sr.myserver.mapper.SysButtonsMapper;
import sr.myserver.mapper.SysMenusMapper;
import sr.myserver.mapper.SysRoleMenuMapper;
import sr.myserver.service.SysMenusService;
import sr.myserver.vo.Menus;
import sr.myserver.vo.SelectData;
import sr.myserver.vo.common.Basic;
import sr.myserver.vo.common.PageRequest;
import sr.myserver.vo.common.PageResponse;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;

/**
 * 菜单信息
 *
 * @author sirui
 **/
@Service
public class SysMenusServiceImpl implements SysMenusService {

    @Autowired
    SysMenusMapper sysMenusMapper;

    @Autowired
    SysButtonsMapper sysButtonsMapper;

    @Autowired
    SysRoleMenuMapper sysRoleMenuMapper;

    /**
     * 查询详情
     *
     * @param id 主键
     * @return 实体对象
     */
    @Override
    public SysMenus get(Serializable id) {
        return sysMenusMapper.selectById(id);
    }

    /**
     * 增加
     *
     * @param entity 请求参数
     * @return 响应码和响应消息
     */
    @Override
    public Basic.Response add(SysMenus entity) {
        sysMenusMapper.insert(entity);
        return Result.ok();
    }

    /**
     * 修改
     *
     * @param entity 请求参数
     * @return 响应码和响应消息
     */
    @Override
    public Basic.Response update(SysMenus entity) {
        sysMenusMapper.updateById(entity);
        return Result.ok();
    }

    /**
     * 删除
     *
     * @param id 主键
     * @return 响应码和响应消息
     */
    @Override
    public Basic.Response deleteById(Serializable id) {
        sysMenusMapper.deleteById(id);
        return Result.ok();
    }

    /**
     * 列表查询
     *
     * @param request 请求参数
     * @return 列表数据集合
     */
    @Override
    public PageResponse<SysMenus> queryTables(PageRequest request) {
        IPage<SysMenus> data = sysMenusMapper.queryTables(request.getPage(), request.getQueryData());
        return new PageResponse(data.getCurrent(), data.getSize(), data.getTotal(), data.getRecords());
    }

    /**
     * 下拉查询
     *
     * @param request 请求参数
     * @return 列表数据集合
     */
    @Override
    public PageResponse<SelectData> querySelect(PageRequest request) {
        IPage<SelectData> data = sysMenusMapper.querySelect(request.getPage(), request.getQueryData());
        return new PageResponse(data.getCurrent(), data.getSize(), data.getTotal(), data.getRecords());
    }

    /**
     * 查询主页菜单
     *
     * @param thinning 用户登录信息
     * @return 用户权限下所有菜单集合
     */
    @Override
    public List<Menus> home(Claims thinning) {
        String roleId = JwtConfig.getRoleId(thinning);
        String[] ids = roleId.split(",");
        List<SysMenus> menus = sysMenusMapper.queryByRoles(ids);
        Collections.sort(menus);
        List<Menus> list = new ArrayList<>();
        for (SysMenus m : menus) {
            if (StringUtils.hasText(m.getSuperId())) {
                continue;
            }
            Menus item = new Menus(m.getTitle(), m.getUrl(), m.getIcon(), m.getId(), null, null);
            item.setChildren(readChild(menus, m, ids));
            list.add(item);
        }
        return list;
    }

    /**
     * 加载权限管理表单菜单
     *
     * @param userId 用户登录Id
     * @return 菜单列表信息
     */
    @Override
    public List<Menus> roles(String userId) {
        List<SysMenus> menus = sysMenusMapper.selectList(null);
        List<Menus> list = new ArrayList<>();
        for (SysMenus m : menus) {
            if (StringUtils.hasText(m.getSuperId())) {
                continue;
            }

            Menus item = new Menus(m.getTitle(), m.getUrl(), m.getIcon(), m.getId(), null, null);
            item.setChildren(readChild(menus, m, null));
            list.add(item);
        }
        return list;
    }

    /**
     * 获取子菜单列表
     *
     * @param data    所有菜单数据
     * @param s       当前菜单
     * @param roleIds 权限编号
     * @return 子菜单信息
     */
    private List<Menus> readChild(List<SysMenus> data, SysMenus s, String[] roleIds) {
        List<Menus> list = new ArrayList<>();
        for (SysMenus m : data) {
            if (m.getSuperId() != null && m.getSuperId().equals(s.getId())) {
                String[] btnId = m.getBtnId().split(",");
                List<SysButtons> buttons = null;
                if (StringUtils.hasText(m.getBtnId()) && !ObjectUtils.isEmpty(roleIds)) {
                    buttons = new ArrayList<>();
                    QueryWrapper<SysRoleMenu> queryWrapper = new QueryWrapper<>();
                    queryWrapper.in("role_id", roleIds);
                    queryWrapper.eq("menu_id", m.getId());
                    SysRoleMenu roleMenu = sysRoleMenuMapper.selectOne(queryWrapper);
                    if (roleMenu != null) {
                        buttons = sysButtonsMapper.queryButtons(Arrays.asList(roleMenu.getButtonIds().split(",")));
                    }
                }
                Menus item = new Menus(m.getTitle(), m.getUrl(), m.getIcon(), m.getId(), btnId, buttons);
                item.setChildren(readChild(data, m, roleIds));
                list.add(item);
            }
        }
        return list;
    }

    /**
     * 功能管理-查询菜单下支持的按钮下拉
     *
     * @param request 请求参数
     * @return 按钮key, value集合
     */
    @Override
    public PageResponse<SelectData> menuSelect(PageRequest request) {
        SysMenus menu = sysMenusMapper.selectById(StrUtils.ots(request.getQueryData().get("of")));
        if (menu == null) {
            return null;
        }
        request.getQueryData().put("ids", Arrays.asList(menu.getBtnId().split(",")));
        IPage<SelectData> data = sysButtonsMapper.querySelect(request.getPage(), request.getQueryData());
        return new PageResponse(data.getCurrent(), data.getSize(), data.getTotal(), data.getRecords());
    }

}
